﻿
// focusDlg.cpp : 实现文件
//

#include "stdafx.h"
#include "focus.h"
#include "focusDlg.h"
#include "afxdialogex.h"
#include "atltypes.h"
#include "afxpanecontainer.h"
#include <windows.h> 
#include <Tlhelp32.h>
#include <psapi.h>
#include <sstream>
#include <string>
#include "Winuser.h"
#include <stdlib.h>
#include <iostream>
#include <Shellapi.h>

using namespace std;

#ifdef _DEBUG
#define new DEBUG_NEW
#endif


HWND nhWnd;

 void CfocusDlg::PrintProcessNameAndID(DWORD processID)
{
    TCHAR szProcessName[MAX_PATH] = TEXT("<unknown>");
	
    // Get a handle to the process.
    HANDLE hProcess = OpenProcess( PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, FALSE, processID );

    // Get the process name.
    if (NULL != hProcess )
    {
        HMODULE hMod;
        DWORD cbNeeded;

        if ( EnumProcessModules( hProcess, &hMod, sizeof(hMod), &cbNeeded) )
        {
            GetModuleBaseName( hProcess, hMod, szProcessName, sizeof(szProcessName)/sizeof(TCHAR) );
        }
    }

    // Print the process name and identifier.
    _tprintf( TEXT("%s  (PID: %u)\n"), szProcessName, processID );

    CloseHandle( hProcess );
}

 /*
 			HANDLE hClose = ::OpenProcess(PROCESS_TERMINATE, FALSE, info.th32ProcessID);
			if (hClose == NULL)
			{
				printf("The Open Process error!");
				return NULL;
			}
			HWND hProcessWnd =(HWND)hClose; //进程的句柄，需要的时候可以返回
 */
 /*由指定的进程名得到相应进程号*/
DWORD CfocusDlg::ProgramID(CString &name)
{
	HANDLE hProcess = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
	if (hProcess == INVALID_HANDLE_VALUE)
	{
		return NULL;
	}

	PROCESSENTRY32 info={0};//这是一个结构体变量,用来存放进程信息的
	info.dwSize = sizeof(PROCESSENTRY32);

	BOOL flag = FALSE;
	flag = Process32First(hProcess, &info);
	while (flag)
	{
		if (0 == wcscmp(name, info.szExeFile))
		{
			CloseHandle(hProcess);
			return info.th32ProcessID;
		}
		flag = Process32Next(hProcess, &info);
	}//endwhile
	CloseHandle(hProcess);
	return NULL;
}





/*EnumWindows的处理函数*/
BOOL CALLBACK EnumWndProc(HWND hwnd, LPARAM lParam)
{

	TCHAR szBuf[MAX_PATH];
	int ret ;
	ret = ::GetWindowText(hwnd, szBuf, MAX_PATH);

	if(NULL != wcsstr(szBuf, (wchar_t *)(lParam)))
	{
		nhWnd = hwnd;
		return false;
	}

	return true;
}

/*根据dwPID得到顶端窗口句柄*/
void CfocusDlg::GetCurTopWindows(CString &name)
{
	EnumWindows((WNDENUMPROC)::EnumWndProc, (LPARAM)name.GetBuffer());
}


 /*判断当前窗口句柄是不是和指定的进程的窗口句柄相同 是TRUE 否FALSE*/
bool CfocusDlg::IsTheSameTopWindowsHWD(CString &name)
{
	HWND hWnd;
    TCHAR szBuf[MAX_PATH];
	int ret;

	hWnd = ::GetForegroundWindow();//得到最前端窗口的句柄
	if (hWnd == NULL )
	   return false;

	ret = ::GetWindowText(hWnd, szBuf, MAX_PATH);
	if(NULL != wcsstr(szBuf, name))
	{
        nhWnd = hWnd;
		return true;
	}

	GetCurTopWindows(name);
	if(0 != nhWnd && hWnd == nhWnd)
	{
		 return true;
	}

	return false;
}

void CfocusDlg::processSupervision(CString &filename, CString &pathname, long timecount)
{
	TCHAR szBuf[MAX_PATH];
	int test;
    bool initial = false;
    bool is_same_window = false;
    int startuptime = 30;
    while(startuptime-- > 0)
    {
        nhWnd = 0;
        is_same_window = IsTheSameTopWindowsHWD(filename);
        if(0 == nhWnd)
        {
            Sleep(1000);
            continue;
        }
        else
            break;
    }
	while(timecount-- >= 0) 
	{
        //memset(szBuf, 0, sizeof(szBuf));
        nhWnd = 0;
        is_same_window = IsTheSameTopWindowsHWD(filename);
        if(0 == nhWnd && initial)
        {
			int msgboxID = ::MessageBox(
					NULL,
					(LPCWSTR)L"已经读完该文档?",
					(LPCWSTR)L"提示",
					MB_YESNOCANCEL
				);

				switch (msgboxID)
				{
				case IDCANCEL:
					return;
				case IDNO:
					if(0 != open_document(pathname))
					{
						MessageBox(_T("打开文档失败！"));
					}
					Sleep(1000);
					continue;
					break;
				case IDYES:
					MessageBox(_T("恭喜"));
					return;
				}
        }

        if(is_same_window)
        {
            CString windowText = _T("");
            if(!initial)
            {
                memset(szBuf, 0, sizeof(szBuf));
                test=::GetWindowText(nhWnd,szBuf,MAX_PATH);
                initial = true;
            }
            
            if(timecount >= 0 )
            {
                windowText.Format(_T("%s\t%d seconds left"),szBuf, timecount);
                            //::MessageBox(nhWnd,windowText.AllocSysString(), 0, 0);
                if(nhWnd != 0)
                {
                    test = ::SetWindowText(nhWnd,windowText.AllocSysString());
                }
                else
                {
                    MessageBox(windowText);
                }
            }
        }
        else
        {
			::SetForegroundWindow(nhWnd);
			::SetWindowPos(nhWnd,HWND_TOPMOST,0,0,0,0,SWP_NOMOVE|SWP_NOSIZE);
			::ShowWindow(nhWnd, SW_SHOWMAXIMIZED);
        }

		Sleep(1000);
	}//end while(1);
}

// 用于应用程序“关于”菜单项的 CAboutDlg 对话框

class CAboutDlg : public CDialogEx
{
public:
	CAboutDlg();

// 对话框数据
	enum { IDD = IDD_ABOUTBOX };

	protected:
	virtual void DoDataExchange(CDataExchange* pDX);    // DDX/DDV 支持

// 实现
protected:
	DECLARE_MESSAGE_MAP()
};

CAboutDlg::CAboutDlg() : CDialogEx(CAboutDlg::IDD)
{
}

void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
}

BEGIN_MESSAGE_MAP(CAboutDlg, CDialogEx)
END_MESSAGE_MAP()


// CfocusDlg 对话框




CfocusDlg::CfocusDlg(CWnd* pParent /*=NULL*/)
	: CDialogEx(CfocusDlg::IDD, pParent), timecount(0), type_reading(_T("")),pathname(_T("")),
    filename(_T(""))
	
{
	m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
}

void CfocusDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
	//DDX_LBString(pDX, IDC_LIST1, type_reading);
}

BEGIN_MESSAGE_MAP(CfocusDlg, CDialogEx)
	ON_WM_SYSCOMMAND()
	ON_WM_PAINT()
	ON_WM_QUERYDRAGICON()
	ON_BN_CLICKED(IDC_BUTTON1, &CfocusDlg::OnBnClickedButton1)
	ON_CBN_SELCHANGE(IDC_COMBO2, &CfocusDlg::OnCbnSelchangeCombo2)
    ON_CBN_SELCHANGE(IDC_COMBO1, &CfocusDlg::OnCbnSelchangeCombo1)
END_MESSAGE_MAP()


// CfocusDlg 消息处理程序

BOOL CfocusDlg::OnInitDialog()
{
	CDialogEx::OnInitDialog();

	// 将“关于...”菜单项添加到系统菜单中。

	// IDM_ABOUTBOX 必须在系统命令范围内。
	ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
	ASSERT(IDM_ABOUTBOX < 0xF000);

	CMenu* pSysMenu = GetSystemMenu(FALSE);
	if (pSysMenu != NULL)
	{
		BOOL bNameValid;
		CString strAboutMenu;
		bNameValid = strAboutMenu.LoadString(IDS_ABOUTBOX);
		ASSERT(bNameValid);
		if (!strAboutMenu.IsEmpty())
		{
			pSysMenu->AppendMenu(MF_SEPARATOR);
			pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
		}
	}

	// 设置此对话框的图标。当应用程序主窗口不是对话框时，框架将自动
	//  执行此操作
	SetIcon(m_hIcon, TRUE);			// 设置大图标
	SetIcon(m_hIcon, FALSE);		// 设置小图标

	// TODO: 在此添加额外的初始化代码
	 ((CComboBox*)GetDlgItem(IDC_COMBO1))->AddString(_T("读书"));
	 ((CComboBox*)GetDlgItem(IDC_COMBO2))->AddString(_T("1"));
	 ((CComboBox*)GetDlgItem(IDC_COMBO2))->AddString(_T("5"));
	 ((CComboBox*)GetDlgItem(IDC_COMBO2))->AddString(_T("10"));
	 ((CComboBox*)GetDlgItem(IDC_COMBO2))->AddString(_T("15"));
	 ((CComboBox*)GetDlgItem(IDC_COMBO2))->AddString(_T("30"));

	// ModifyStyle(WS_CAPTION,0,0);   //如果不想去掉标题栏，去掉该句。
    //SendMessage(WM_SYSCOMMAND,SC_MAXIMIZE,0); //不显示任务栏
     //ShowWindow(SW_MAXIMIZE);//显示任务栏

	 //OnFullScreen();
      //SetWindowPos(nhWnd,HWND_TOPMOST,0,0,0,0,SWP_NOMOVE|SWP_NOSIZE);
     
	return TRUE;  // 除非将焦点设置到控件，否则返回 TRUE
}

void CfocusDlg::OnSysCommand(UINT nID, LPARAM lParam)
{
	if ((nID & 0xFFF0) == IDM_ABOUTBOX)
	{
		CAboutDlg dlgAbout;
		dlgAbout.DoModal();
	}
	else
	{
		CDialogEx::OnSysCommand(nID, lParam);
	}
}

// 如果向对话框添加最小化按钮，则需要下面的代码
//  来绘制该图标。对于使用文档/视图模型的 MFC 应用程序，
//  这将由框架自动完成。

void CfocusDlg::OnPaint()
{
	if (IsIconic())
	{
		CPaintDC dc(this); // 用于绘制的设备上下文

		SendMessage(WM_ICONERASEBKGND, reinterpret_cast<WPARAM>(dc.GetSafeHdc()), 0);

		// 使图标在工作区矩形中居中
		int cxIcon = GetSystemMetrics(SM_CXICON);
		int cyIcon = GetSystemMetrics(SM_CYICON);
		CRect rect;
		GetClientRect(&rect);
		int x = (rect.Width() - cxIcon + 1) / 2;
		int y = (rect.Height() - cyIcon + 1) / 2;

		// 绘制图标
		dc.DrawIcon(x, y, m_hIcon);
	}
	else
	{
		CDialogEx::OnPaint();
	}
}

//当用户拖动最小化窗口时系统调用此函数取得光标
//显示。
HCURSOR CfocusDlg::OnQueryDragIcon()
{
	return static_cast<HCURSOR>(m_hIcon);
}

void CfocusDlg::OnFullScreen(bool m_bFullScreen)     
{

    LONG style = ::GetWindowLong(this->m_hWnd,GWL_STYLE);
    if(m_bFullScreen)
    {
        style &= ~(WS_DLGFRAME | WS_THICKFRAME);
        SetWindowLong(this->m_hWnd,GWL_STYLE, style);
        this->ShowWindow(SW_SHOWMAXIMIZED);
       
        this->GetWindowRect(&rect);
        ::SetWindowPos(this->m_hWnd,HWND_TOPMOST,rect.left-1, rect.top-1, rect.right-rect.left + 3, rect.bottom-rect.top + 3, SWP_FRAMECHANGED);
        //::SetWindowPos(m_hWnd,HWND_TOPMOST,0,0,0,0,SWP_NOMOVE|SWP_NOSIZE);
    }
    else
    {
        //style |= WS_DLGFRAME | WS_THICKFRAME;
        //SetWindowLong(this->m_hWnd, GWL_STYLE, style);
        ::SetWindowPos(this->m_hWnd,HWND_NOTOPMOST,rect.left-1, rect.top-1, rect.right-rect.left + 3, rect.bottom-rect.top + 3, SWP_NOMOVE|SWP_NOSIZE);
        //::SetWindowPos(this->m_hWnd,HWND_NOTOPMOST,0,0,0,0,SWP_NOMOVE|SWP_NOSIZE);
        //this->ShowWindow(SW_NORMAL);
    }
}

LPCTSTR CfocusDlg::get_doc_type()
{
    CString doc_type;
    CString file_ext;
    file_ext = _T("*.txt");
    file_ext.Append(_T("; *.doc"));
    file_ext.Append(_T("; *.docx"));
    file_ext.Append(_T("; *.xlsx"));
    file_ext.Append(_T("; *.xls"));
    file_ext.Append(_T("; *.pdf"));
    file_ext.Append(_T("; *.chm"));
    file_ext.Append(_T("; *.html"));
    file_ext.Append(_T("; *.htm"));

    doc_type = _T("Document Files (") + file_ext +  _T(")|") + file_ext + _T("||");

    return doc_type.AllocSysString();
}

int CfocusDlg::open_document(CString &file_name)
{
    SHELLEXECUTEINFO  ExecInfo;
    ZeroMemory(&ExecInfo, sizeof(SHELLEXECUTEINFO));
    ExecInfo.cbSize = sizeof(SHELLEXECUTEINFO);
    ExecInfo.hwnd = NULL;
    ExecInfo.lpFile = file_name.AllocSysString();
    ExecInfo.nShow = SW_SHOWMAXIMIZED;
    ExecInfo.lpVerb = _T("open");
    ExecInfo.fMask = SEE_MASK_NOCLOSEPROCESS ;

    if(!ShellExecuteEx(&ExecInfo))
    {
        MessageBox(_T("打开文件失败"));
        return -1;
    }

    return 0;
    ///WaitForSingleObject(ExecInfo.hProcess, INFINITE);


}

void CfocusDlg::OnBnClickedButton1()
{
	// TODO: Add your control notification handler code here
    if(0 == timecount || type_reading == _T(""))
    {
        MessageBox(_T("请选择项目及时间！"));
        return;
    }
    

    CFileDialog   dlg(TRUE, NULL, NULL, OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT, get_doc_type(), NULL, 0); 
	if(dlg.DoModal()==IDOK) 
	{
		pathname = dlg.GetPathName();
		filename = dlg.GetFileName(); 

        OnFullScreen(false);
        if( 0 != open_document(pathname) )
        {
            MessageBox(_T("打开文档失败！"));
        }
		/*if(32 >= (int)ShellExecuteEx(NULL, _T("open"), pathname, NULL,NULL,SW_SHOWMAXIMIZED))
        {
            MessageBox(_T("打开文档失败！"));
        }*/
        Sleep(1000);
        //m_bFullScreen = false;
        OnFullScreen(false);
		processSupervision(filename, pathname, timecount);
	}
}


void CfocusDlg::OnCbnSelchangeCombo2()
{
	// TODO: Add your control notification handler code here
	CString strTemp;
	((CComboBox*)GetDlgItem(IDC_COMBO2))->GetWindowText(strTemp);
	//int i;
	int j = _stscanf(strTemp, _T("%d"), &timecount);
	timecount = timecount * 60;

}


void CfocusDlg::OnCbnSelchangeCombo1()
{
    // TODO: Add your control notification handler code here
    ((CComboBox*)GetDlgItem(IDC_COMBO1))->GetWindowText(type_reading);
}
